package com.ikangtai.shecare.common.db;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;

import com.ikangtai.shecare.common.App;
import com.ikangtai.shecare.common.CollectedArticle;
import com.ikangtai.shecare.common.al.CycleUnitDS;
import com.ikangtai.shecare.common.al.DayUnitDSInput;
import com.ikangtai.shecare.common.al.DayUnitDSOutput;
import com.ikangtai.shecare.common.al.UserUnitDS;
import com.ikangtai.shecare.common.baseView.collectionList.CollectionBean;
import com.ikangtai.shecare.common.db.sync.HealthInfo;
import com.ikangtai.shecare.common.eventBusMsg.RecordInfo;
import com.ikangtai.shecare.common.util.AppLog;
import com.ikangtai.shecare.common.util.DateUtil;
import com.ikangtai.shecare.common.util.TasksUtil;
import com.ikangtai.shecare.home.HomeSysTask;
import com.ikangtai.shecare.record.bean.UserRecordData;
import com.ikangtai.shecare.record.bean.UserTemperatureInfo;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

public class DBManager {

    private DatabaseHelper helper;
    private SQLiteDatabase db;

    public DBManager(Context context) {
        helper = DatabaseHelper.getInstance(context);
        // 因为getWritableDatabase内部调用了mContext.openOrCreateDatabase(mName, 0,
        // mFactory);
        // 所以要确保context已初始化,我们可以把实例化DBManager的步骤放在Activity的onCreate里

        db = helper.getWritableDatabase();
    }

    public SQLiteDatabase getSQLiteDatabase() {
        return db;
    }

    /**
     * *****************
     * 数据库基础操作方法
     * *****************
     */

    public synchronized void insertUserPreference(String userName, String userPswd) {
        ContentValues values = new ContentValues();
        values.put("userName", userName);
        values.put("userPswd", userPswd);
        db.replace(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, null, values);
    }

    // 使用此方法获取用户db某个key的唯一值
    public String getSqliteKeyValue(String userName, String columnName) {
        Cursor cursor = db.rawQuery("SELECT " + columnName + " FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "'", null);

        String value = null;
        while (cursor.moveToNext()) {
            value = cursor.getString(cursor.getColumnIndex(columnName));
        }

        cursor.close();

        return value;
    }

    public synchronized void updateUserPreference(String userName, String columnName, String columnValue) {
        updateUserPreference(userName, columnName, columnValue, null, 0);
    }

    public synchronized void updateUserPreference(String userName, String columnName, String columnValue, String syncColumnName, int isSynced) {
        ContentValues values = new ContentValues();
        values.put(columnName, columnValue);

        // null 表明DB里没有也不需要为此字段设置相应的sync字段
        if (syncColumnName != null)
            values.put(syncColumnName, isSynced);

        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ?", new String[]{userName});
    }

    public synchronized void updateUserPrefList(String userName, ArrayList<String> columnName, ArrayList<String> columnValue, String syncColumnName, int isSynced) {
        ContentValues values = new ContentValues();
        for (int i = 0; i < columnName.size(); i++)
            values.put(columnName.get(i), columnValue.get(i));

        values.put(syncColumnName, isSynced);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ?", new String[]{userName});
    }

    public synchronized boolean hasUser(String userName) {
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "'", null);
        return (cursor.getCount() != 0) ? true : false;
    }

    public synchronized void initUserPreferences2Memory(String userName) {
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "'", null);

        while (cursor.moveToNext()) {
            App.memory_preference_nickName = cursor.getString(cursor.getColumnIndex("nickName"));
            App.memory_preference_userState = cursor.getInt(cursor.getColumnIndex("state"));
            App.memory_preference_birthday = cursor.getString(cursor.getColumnIndex("birthday"));
            App.memory_preference_periodLen = cursor.getInt(cursor.getColumnIndex("periodLen"));
            App.memory_preference_mensesLen = cursor.getInt(cursor.getColumnIndex("mensesLen"));
            App.memory_preference_mensesType = cursor.getInt(cursor.getColumnIndex("mensesType"));
            App.memory_preference_lastPeriodDate = cursor.getString(cursor.getColumnIndex("lastPeriodDate"));
            App.memory_preference_macAddress = cursor.getString(cursor.getColumnIndex("macAddress"));
            App.memory_preference_taskIDs = cursor.getString(cursor.getColumnIndex("taskIDs"));
            App.memory_preference_isDataDownloaded = cursor.getString(cursor.getColumnIndex("isDataDownloaded"));
            App.memory_preference_lastConnectTime = cursor.getString(cursor.getColumnIndex("lastConnectTime"));
        }
        cursor.close();
    }

    public synchronized int getTemperatureNum(String userName, long measureTime) {

        String time = DateUtil.getDateStr2bit(measureTime);
        long timeDayStart = DateUtil.getStringToDate(time + " 00:00:00");
        long timeDayEnd = DateUtil.getStringToDate(time + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + timeDayStart + " AND measureTime <= " + timeDayEnd + " AND isDelete = 0 ", null);
        return cursor.getCount();

    }

    public synchronized boolean checkTemperatureIsUploaded(String userName, long measureTime) {

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime = " + measureTime + " AND isDelete = 0 ", null);
        return (cursor.getCount() != 0) ? true : false;

    }

    public synchronized List<UserTemperatureInfo> getSelectedDayTemperature(String userName, String dateString) {
        List<UserTemperatureInfo> userTemperatureInfos = new ArrayList<>();
        UserTemperatureInfo userTemperatureInfo = null;
        long timeDayStart = DateUtil.getStringToDate(dateString + " 00:00:00");
        long timeDayEnd = DateUtil.getStringToDate(dateString + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + timeDayStart + " AND measureTime <= " + timeDayEnd + " AND isDelete = 0 ", null);

        while (cursor.moveToNext()) {
            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            userTemperatureInfos.add(userTemperatureInfo);
        }

        cursor.close();
        if (userTemperatureInfos.size() > 1 && userTemperatureInfos.get(0).getIsBBT() != 1) {
            for (int i = 1; i < userTemperatureInfos.size(); i++) {
                if (userTemperatureInfos.get(i).getIsBBT() == 1) {
                    UserTemperatureInfo userTemperatureInfoRefer = userTemperatureInfos.get(0);
                    userTemperatureInfos.set(0, userTemperatureInfos.get(i));
                    userTemperatureInfos.set(i, userTemperatureInfoRefer);
                    break;
                }
            }
        }

        return userTemperatureInfos;
    }

    public synchronized UserTemperatureInfo getSelectedDayBBTTemperature(String userName, String dateString) {

        UserTemperatureInfo userTemperatureInfo = new UserTemperatureInfo();
        long timeDayStart = DateUtil.getStringToDate(dateString + " 00:00:00");
        long timeDayEnd = DateUtil.getStringToDate(dateString + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + timeDayStart + " AND measureTime <= " + timeDayEnd + " AND isDelete = 0 " + " AND isBBT = 1 ", null);

        while (cursor.moveToNext()) {
//            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));

        }
        cursor.close();
        return userTemperatureInfo;
    }

    public synchronized List<UserTemperatureInfo> getBBTDataList(String userName, long startTime, long endTime) {
        long startTimeTwelfth = DateUtil.getStringToDate(DateUtil.getDateStr2bit(startTime) + " 12:00:00");
        long endTimeTwelfth = DateUtil.getStringToDate(DateUtil.getDateStr2bit(endTime) + " 12:00:00");
        int size = (int) ((endTimeTwelfth - startTimeTwelfth) / (24 * 3600)) + 1;
        List<UserTemperatureInfo> everydayUserTemperatureInfoList = new ArrayList<UserTemperatureInfo>();
        List<UserTemperatureInfo> userTemperatureInfos = new ArrayList<UserTemperatureInfo>();
        long recordStratTime = DateUtil.getStringToDate(DateUtil.getDateStr2bit(startTime) + " 00:00:00");
        long recordEndTime = DateUtil.getStringToDate(DateUtil.getDateStr2bit(endTime) + " 23:59:59");
        UserTemperatureInfo userTemperatureInfo = null;

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + recordStratTime + " AND measureTime <= " + recordEndTime + " AND isDelete = 0 " + " AND isBBT = 1 ", null);

        while (cursor.moveToNext()) {
            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            userTemperatureInfos.add(userTemperatureInfo);
        }

        cursor.close();

        // 由于数据库不是每天都有BBT，而为了和DayOutput大圆圈的个数一致，因此对于没有BBT的日期则填充默认的BBT=0, isBBT=0的值。
        for (int i = 0; i < size; i++) {
            userTemperatureInfo = new UserTemperatureInfo();
            long date = startTimeTwelfth + i * 24 * 3600;
            userTemperatureInfo.setMeasureTime(date);
            long timeDayStart = DateUtil.getStringToDate(DateUtil.getDateStr2bit(date) + " 00:00:00");
            long timeDayEnd = DateUtil.getStringToDate(DateUtil.getDateStr2bit(date) + " 23:59:59");
            for (int j = 0; j < userTemperatureInfos.size(); j++) {
                if (userTemperatureInfos.get(j).getMeasureTime() >= timeDayStart && userTemperatureInfos.get(j).getMeasureTime() <= timeDayEnd) {
                    userTemperatureInfo = userTemperatureInfos.get(j);
                    break;
                }
            }
            everydayUserTemperatureInfoList.add(userTemperatureInfo);
        }
        return everydayUserTemperatureInfoList;
    }

    public synchronized List<UserTemperatureInfo> getTemperatureList(String userName, long startTime) {
        List<UserTemperatureInfo> userTemperatureInfos = new ArrayList<>();
        UserTemperatureInfo userTemperatureInfo = null;

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + startTime + " AND isBBT = 1 AND isDelete = 0 " + " ORDER BY measureTime ASC", null);

        while (cursor.moveToNext()) {
            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            userTemperatureInfos.add(userTemperatureInfo);
        }

        cursor.close();
        return userTemperatureInfos;
    }

    public synchronized List<UserTemperatureInfo> getTemperatureList(String userName, long startTime, long endTime) {
        List<UserTemperatureInfo> userTemperatureInfos = new ArrayList<>();
        UserTemperatureInfo userTemperatureInfo = null;

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND measureTime >= " + startTime + " AND measureTime < " + endTime + " AND isBBT = 1 AND isDelete = 0 " + " ORDER BY measureTime ASC", null);

        while (cursor.moveToNext()) {
            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            userTemperatureInfos.add(userTemperatureInfo);
        }

        cursor.close();
        return userTemperatureInfos;
    }

    public synchronized List<UserTemperatureInfo> getUnsyncedTemperatureList(String userName) {
        List<UserTemperatureInfo> userTemperatureInfos = new ArrayList<UserTemperatureInfo>();
        UserTemperatureInfo userTemperatureInfo = null;

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.TEMPERATURE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0 " + " AND measureTime > 1420070400" + " AND isDelete = 0 ", null);

        while (cursor.moveToNext()) {
            userTemperatureInfo = new UserTemperatureInfo();
            userTemperatureInfo.setTemperatureId(cursor.getString(cursor.getColumnIndex("temperatureId")));
            userTemperatureInfo.setUserName(App.userName);
            userTemperatureInfo.setMeasureTime(cursor.getLong(cursor.getColumnIndex("measureTime")));
            userTemperatureInfo.setEditTime(cursor.getLong(cursor.getColumnIndex("editTime")));
            userTemperatureInfo.setTemperature(cursor.getDouble(cursor.getColumnIndex("temperature")));
            userTemperatureInfo.setIsBBT(cursor.getInt(cursor.getColumnIndex("isBBT")));
            userTemperatureInfo.setType(cursor.getInt(cursor.getColumnIndex("type")));
            //userTemperatureInfo.setSyncType(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userTemperatureInfo.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            userTemperatureInfos.add(userTemperatureInfo);
        }

        cursor.close();
        return userTemperatureInfos;
    }


    public synchronized UserRecordData getSelectedDayRecordData(String userName, String dateString) {
        UserRecordData userRecordData = new UserRecordData();
        long timeDayStart = DateUtil.getStringToDate(dateString + " 00:00:00");
        long timeDayEnd = DateUtil.getStringToDate(dateString + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' AND recordDate >= " + timeDayStart + " AND recordDate <= " + timeDayEnd, null);

        while (cursor.moveToNext()) {
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            userRecordData.setLHResult(cursor.getInt(cursor.getColumnIndex("LHResult")));
            userRecordData.setHCGResult(cursor.getInt(cursor.getColumnIndex("HCGResult")));
            userRecordData.setIsOvulationDay(cursor.getInt(cursor.getColumnIndex("isOvulationDay")));
            //userRecordData.setIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
        }

        cursor.close();
        return userRecordData;
    }

    public synchronized UserRecordData getLastMensesRecordData(String userName) {
        List<UserRecordData> userRecordDataList = new ArrayList<UserRecordData>();
        UserRecordData userRecordData = null;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' AND mensesInfo != 0 ", null);

        while (cursor.moveToNext()) {
            userRecordData = new UserRecordData();
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordDataList.add(userRecordData);
        }
        cursor.close();
        AppLog.i("用户的月经开始记录数：" + userRecordDataList.size());
        if (userRecordDataList.size() == 0) {
//            userRecordData = new UserRecordData();
//            userRecordData.setRecordDate(new Date().getTime() / 1000 - 28 * 24 * 3600);
//            userRecordData.setMensesInfo(1);
            return null;
        } else if (userRecordDataList.size() == 1) {
            return userRecordDataList.get(0);
        } else {
            UserRecordData userRecordData1 = new UserRecordData();
            userRecordData1.setRecordDate(userRecordDataList.get(0).getRecordDate());
            userRecordData1.setMensesInfo(userRecordDataList.get(0).getMensesInfo());
            for (int i = 1; i < userRecordDataList.size(); i++) {
                if (userRecordDataList.get(i).getRecordDate() > userRecordData1.getRecordDate() && UserRecordData.isMensesBlood(userRecordDataList.get(i).getMensesInfo())) {
                    userRecordData1.setRecordDate(userRecordDataList.get(i).getRecordDate());
                    userRecordData1.setMensesInfo(userRecordDataList.get(i).getMensesInfo());
                }
            }
        AppLog.e("userRecordData1 getRecordDate:" + userRecordData1.getRecordDate() + " getMensesInfo:" + userRecordData1.getMensesInfo());
            long endTime = DateUtil.getStringToDate(DateUtil.getDateStr2bit(userRecordData1.getRecordDate()) + " 00:00:00");
            long startTime = endTime - 9 * 24 * 3600;
            List<UserRecordData> userRecordDataList1 = getRecordDataList(App.userName, startTime, endTime);
            if (null != userRecordDataList1 && 0 != userRecordDataList1.size()) {
                for (int j = 0; j < userRecordDataList1.size(); j++) {
                    if (userRecordDataList1.get(j).getRecordDate() < userRecordData1.getRecordDate() && UserRecordData.isMensesBlood(userRecordDataList1.get(j).getMensesInfo())) {
                        userRecordData1.setRecordDate(userRecordDataList1.get(j).getRecordDate());
                        userRecordData1.setMensesInfo(userRecordDataList1.get(j).getMensesInfo());
                    }
                }
            }

            AppLog.i("用户的月经开始记录：" + userRecordData1.getRecordDate());
            return userRecordData1;
        }
    }

    public synchronized void setSelectedDayRecordDataInfo(UserRecordData userRecordData) {
        long dayTime = userRecordData.getDayTime();
        String dateString = DateUtil.getDateStr2bit(dayTime);
        long timeDayStart = DateUtil.getStringToDate(dateString + " 00:00:00");
        long timeDayEnd = DateUtil.getStringToDate(dateString + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + App.userName + "' AND recordDate >= " + timeDayStart + " AND recordDate <= " + timeDayEnd, null);

        while (cursor.moveToNext()) {
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            //userRecordData.setIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
        }
        cursor.close();
    }

    public synchronized List<UserRecordData> getRecordDataList(String userName, long startTime) {
        List<UserRecordData> userRecordDataList = new ArrayList<UserRecordData>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' AND recordDate >= " + startTime + " ORDER BY recordDate ASC", null);
        UserRecordData userRecordData = null;

        while (cursor.moveToNext()) {
            userRecordData = new UserRecordData();
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            //userRecordData.setIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userRecordDataList.add(userRecordData);
        }

        cursor.close();
        return userRecordDataList;
    }

    public synchronized List<UserRecordData> getRecordDataList(String userName, long startTime, long endTime) {
        long startTimeTwelfth = DateUtil.getStringToDate(DateUtil.getDateStr2bit(startTime) + " 12:00:00");
        long endTimeTwelfth = DateUtil.getStringToDate(DateUtil.getDateStr2bit(endTime) + " 12:00:00");
        int size = (int) ((endTimeTwelfth - startTimeTwelfth) / (24 * 3600)) + 1;
        List<UserRecordData> everydayUserRecordDataList = new ArrayList<UserRecordData>();
        List<UserRecordData> userRecordDataList = new ArrayList<UserRecordData>();
        long recordStratTime = DateUtil.getStringToDate(DateUtil.getDateStr2bit(startTime) + " 00:00:00");
        long recordEndTime = DateUtil.getStringToDate(DateUtil.getDateStr2bit(endTime) + " 23:59:59");
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' AND recordDate >= " + recordStratTime + " AND recordDate <= " + recordEndTime, null);
        AppLog.i("cursor size:" + cursor.getCount());
        UserRecordData userRecordData = null;

        while (cursor.moveToNext()) {
            userRecordData = new UserRecordData();
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            //userRecordData.setIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
            userRecordDataList.add(userRecordData);
        }

        cursor.close();
        AppLog.i("userRecordDataList size:" + userRecordDataList.size());

        for (int i = 0; i < size; i++) {
            userRecordData = new UserRecordData();
            long date = startTimeTwelfth + i * 24 * 3600;
            userRecordData.setRecordDate(date);
            long timeDayStart = DateUtil.getStringToDate(DateUtil.getDateStr2bit(date) + " 00:00:00");
            long timeDayEnd = DateUtil.getStringToDate(DateUtil.getDateStr2bit(date) + " 23:59:59");
            for (int j = 0; j < userRecordDataList.size(); j++) {
                if (userRecordDataList.get(j).getRecordDate() >= timeDayStart && userRecordDataList.get(j).getRecordDate() <= timeDayEnd) {
                    userRecordData = userRecordDataList.get(j);
                    break;
                }
            }
            everydayUserRecordDataList.add(userRecordData);
        }

        return everydayUserRecordDataList;
    }

    public synchronized void initCollectionIDs2Memory(String userName) {
        App.collectedArticleIdList.clear();
        App.articleId2CollectionIDMap.clear();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.COLLECTION_TABLE_NAME + " WHERE userName = '" + userName + "'" + " AND collectionDelete = 0 ", null);

        while (cursor.moveToNext()) {
            String collectionID = cursor.getString(cursor.getColumnIndex("collectionID"));
            String collectionURL = cursor.getString(cursor.getColumnIndex("articleId"));

            App.collectedArticleIdList.add(collectionURL);
            App.articleId2CollectionIDMap.put(collectionURL, collectionID);
        }

        cursor.close();
    }

    /**
     * add collectedArticles
     * 用户第一次安装时触发, 批量下载
     * server只会给delete为0的收藏，所以这里CollectedArticle.collectionDelete = 0
     *
     * @param collectedArticles
     */
    public synchronized void add(List<CollectedArticle> collectedArticles) {
        AppLog.i("DBManager --> add collectedArticles");
        // 采用事务处理，确保数据完整性
        db.beginTransaction(); // 开始事务

        try {
            for (CollectedArticle collectedArticle : collectedArticles) {
                db.execSQL("REPLACE INTO " + DatabaseHelper.COLLECTION_TABLE_NAME
                        + " VALUES(?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{collectedArticle.collectionID,
                        collectedArticle.collectionName, collectedArticle.collectionURL, collectedArticle.collectionFrom,
                        collectedArticle.collectionDate, collectedArticle.collectionDelete, App.userName, 1});
            }

            db.setTransactionSuccessful(); // 设置事务成功完成
        } finally {
            db.endTransaction(); // 结束事务
        }
    }

    /**
     * 删除收藏到本地数据库
     */
    public synchronized void addOrDelete(CollectedArticle collectedArticle, int isSynced) {
        AppLog.i("collectionID=" + collectedArticle.collectionID +
                ",collectionName=" + collectedArticle.collectionName +
                ",collectionURL=" + collectedArticle.collectionURL +
                ",collectionFrom=" + collectedArticle.collectionFrom +
                ",collectionDate=" + collectedArticle.collectionDate +
                ",collectionDelete=" + collectedArticle.collectionDelete +
                ",userName=" + App.userName +
                ",isSynced=" + isSynced);
        db.execSQL("REPLACE INTO " + DatabaseHelper.COLLECTION_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{collectedArticle.collectionID,
                collectedArticle.collectionName, collectedArticle.collectionURL, collectedArticle.collectionFrom,
                collectedArticle.collectionDate, collectedArticle.collectionDelete, App.userName, isSynced});

        App.articleId2CollectionIDMap.put(collectedArticle.collectionURL, collectedArticle.collectionID);
        App.collectedArticleIdList.add(collectedArticle.collectionURL);
    }

    public synchronized List<CollectionBean> getCollectionArticles(String userName) {
        List<CollectionBean> collectionBeanList = new ArrayList<CollectionBean>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.COLLECTION_TABLE_NAME + " WHERE userName = '" + userName + "' and collectionDelete = 0", null);

        while (cursor.moveToNext()) {
            CollectionBean collectionBean = new CollectionBean();

            String collectionID = cursor.getString(cursor.getColumnIndex("collectionID"));
            String collectionTitle = cursor.getString(cursor.getColumnIndex("articleTitle"));
            int articleId = cursor.getInt(cursor.getColumnIndex("articleId"));
            String collectionDate = cursor.getString(cursor.getColumnIndex("collectionDate"));

            collectionBean.setCollectionID(collectionID);
            collectionBean.setCollectionTitle(collectionTitle);
            collectionBean.setArticleId(articleId);
            collectionBean.setCollectionDate(collectionDate);

            collectionBeanList.add(collectionBean);
        }

        cursor.close();

        return collectionBeanList;
    }

    public synchronized void saveTempearatureData(UserTemperatureInfo userTemperatureInfo) {
        AppLog.i("sqi save temper data success");
        db.execSQL("REPLACE INTO " + DatabaseHelper.TEMPERATURE_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?, ?, ?, ?,?)", new Object[]{userTemperatureInfo.getTemperatureId(),
                userTemperatureInfo.getUserName(), userTemperatureInfo.getMeasureTime(), userTemperatureInfo.getEditTime(),
                userTemperatureInfo.getTemperature(), userTemperatureInfo.getIsBBT(), userTemperatureInfo.getType(), userTemperatureInfo.getSyncType(), userTemperatureInfo.getIsDelete()});

    }

    public synchronized void saveRecordData(UserRecordData userRecordData) {
        AppLog.i("sqi save record data success");
        db.execSQL("REPLACE INTO " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{userRecordData.getId(),
                userRecordData.getUserName(), userRecordData.getRecordDate(), userRecordData.getRecordEditDate(),
                userRecordData.getSymptomInfo(), userRecordData.getMucusInfo(), userRecordData.getMensesInfo(),
                userRecordData.getCopulationInfo(), userRecordData.getOvulationInfo(), userRecordData.getSexTime(), userRecordData.getMemoInfo(), userRecordData.getIsSynced(), userRecordData.getLHResult(), userRecordData.getHCGResult(), userRecordData.getIsOvulationDay()});
    }

    /**
     * ******************************
     * 算法相关
     * ******************************
     */

    public synchronized void saveALUserData(UserUnitDS userData, int isSynced) {
        AppLog.i("start saveALUserData!");

        db.execSQL("REPLACE INTO " + DatabaseHelper.AL_USERDATA_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{App.userName, userData.validCycleCount, userData.averageMenstruationLength,
                userData.menstruationLengthError, userData.averageCycleLength, userData.cycleLengthError,
                userData.averageLuteumPhaseLength, userData.averageOvulationDay, userData.abnormalCaseAlert, isSynced});
    }

    public synchronized void saveALDayOutput(List<DayUnitDSOutput> alDayOutputList, int isSynced) {
        AppLog.i("start saveALDayOutput!");

        db.beginTransaction();

        try {
            for (int i = 0; i < alDayOutputList.size(); i++) {
                AppLog.i("dayOutput.length = " + alDayOutputList.size() + ", dayOutput[" + i + "].date:" + DateUtil.getDateTimeStr2bit(alDayOutputList.get(i).date) + ", alDayOutputList.get(i).periodAchieveConfirm:" + alDayOutputList.get(i).periodAchieveConfirm);

                if (!DateUtil.isValidDate(alDayOutputList.get(i).date)) continue;

                db.execSQL("REPLACE INTO " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME
                        + " VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{App.userName, alDayOutputList.get(i).periodAchieveForecast, alDayOutputList.get(i).periodAchieveConfirm,
                        alDayOutputList.get(i).periodAvoidForecast, alDayOutputList.get(i).periodAvoidConfirm,
                        alDayOutputList.get(i).homePageMenstruationEnd, alDayOutputList.get(i).homePageOvulation,
                        alDayOutputList.get(i).homePageConceptionChance, alDayOutputList.get(i).homePageNextMenstruation,
                        alDayOutputList.get(i).date, alDayOutputList.get(i).dayOfCycle, isSynced});
            }

            db.setTransactionSuccessful(); // 设置事务成功完成
        } finally {
            db.endTransaction(); // 结束事务
        }
    }

    public synchronized void saveALCycleOutput(CycleUnitDS[] cycleOutput, int isSynced) {
        AppLog.i("start saveALCycleOutput!");

        db.beginTransaction(); // 开始事务

        try {
            for (int i = 0; i < cycleOutput.length; i++) {
                cycleOutput[i].showLog();
                if (cycleOutput[i].cycleNumber == -10) {
                    AppLog.i("cycleOutput[i].cycleNumber is -10, continue!");
                    continue;
                }

                db.execSQL("REPLACE INTO " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME
                        + " VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", new Object[]{
                        App.userName,
                        cycleOutput[i].menstruationStartForecast,
                        cycleOutput[i].menstruationEndForecast,
                        cycleOutput[i].menstruationStartConfirm,
                        cycleOutput[i].menstruationEndConfirm,
                        cycleOutput[i].BBTRiseDay,
                        cycleOutput[i].peakDay,
                        cycleOutput[i].ovulationDayForecast,
                        cycleOutput[i].ovulationDayConfirm,
                        cycleOutput[i].ovulationDayUserRecord,
                        cycleOutput[i].ovulationDayBBTRise,
                        cycleOutput[i].ovulationDayNextMenstruation,
                        cycleOutput[i].fertileWindowStartForecast,
                        cycleOutput[i].fertileWindowEndForecast,
                        cycleOutput[i].fertileWindowStartConfirm,
                        cycleOutput[i].fertileWindowEndConfirm,
                        cycleOutput[i].dangerWindowStartForecast,
                        cycleOutput[i].dangerWindowEndForecast,
                        cycleOutput[i].dangerWindowStartConfirm,
                        cycleOutput[i].dangerWindowEndConfirm,
                        cycleOutput[i].nextMenstruationStartForecast,
                        cycleOutput[i].nextMenstruationEndForecast,
                        cycleOutput[i].nextOvulationDayForecast,
                        cycleOutput[i].nextFertileWindowStartForecast,
                        cycleOutput[i].nextFertileWindowEndForecast,
                        cycleOutput[i].nextDangerWindowStartForecast,
                        cycleOutput[i].nextDangerWindowEndForecast,
                        cycleOutput[i].cycleNumber,
                        cycleOutput[i].ovulationDayUserRecordBasis, isSynced});
            }

            db.setTransactionSuccessful(); // 设置事务成功完成
        } finally {
            db.endTransaction(); // 结束事务
        }
    }

    public synchronized int getSelectedDayCycleUnitDSNum(String userName, long recordDate) {
        int num = 0;
        CycleUnitDS[] cycles = getALCycleOutput(App.userName, null);
        long[] startMenses = new long[cycles.length];
        for(int i = 0; i < cycles.length; i ++){
            if(cycles[i].menstruationStartConfirm > 0){
                startMenses[i] = cycles[i].menstruationStartConfirm;
            }else{
                startMenses[i] = cycles[i].menstruationStartForecast;
            }
        }

        for(int i = 0; i < startMenses.length - 1; i++){
            if(recordDate >= startMenses[i] && recordDate < startMenses[i + 1]){
                num = cycles[i].cycleNumber;
                break;
            }else num = cycles[startMenses.length - 1].cycleNumber;
        }

        return num;
    }

    public synchronized CycleUnitDS[] getCurrentDayCycle(String userName) {

        int num = -1;
        long currentDate = new Date().getTime() / 1000;
        CycleUnitDS[] cycles = getALCycleOutput(App.userName, null);
        long[] startMenses = new long[cycles.length];
        for(int i = 0; i < cycles.length; i++){
            if(cycles[i].menstruationStartConfirm > 0){
                startMenses[i] = cycles[i].menstruationStartConfirm;
            }else{
                startMenses[i] = cycles[i].menstruationStartForecast;
            }
        }
        for(int i = 0; i < startMenses.length - 1; i++){
            if(currentDate >= startMenses[i] && currentDate < startMenses[i + 1]){
                num = i;
                AppLog.e("currentCycle num:" + cycles[i].cycleNumber);
                break;
            }
        }
        if(num < 0) return null;
        CycleUnitDS[] currentCycle = new CycleUnitDS[1];
        currentCycle[0] = cycles[num];

        return currentCycle;
    }

    public synchronized long getSelectedDayCycleUnitDSMensesStartConfirm(String userName, long recordDate) {

        long timeStamp = 0;
        CycleUnitDS[] cycles = getALCycleOutput(App.userName, null);
        long[] startMenses = new long[cycles.length];
        for(int i = 0; i < cycles.length; i ++){
            if(cycles[i].menstruationStartConfirm > 0){
                startMenses[i] = cycles[i].menstruationStartConfirm;
            }else{
                startMenses[i] = cycles[i].menstruationStartForecast;
            }
        }

        for(int i = 0; i < startMenses.length - 1; i++){
            if(recordDate >= startMenses[i] && recordDate < startMenses[i + 1]){
                timeStamp = startMenses[i];
                break;
            }else timeStamp = startMenses[startMenses.length - 1];
        }

        return timeStamp;
    }

    public synchronized long getCycleUnitDSMensesFirstStartConfirm(String userName) {

        long timeStamp = 0;
        CycleUnitDS[] cycles = getALCycleOutput(App.userName, null);
        for(int i = 0; i < cycles.length; i ++){
            if(cycles[i].menstruationStartConfirm > 0){
                timeStamp = cycles[i].menstruationStartConfirm;
                break;
            }
        }
        return timeStamp;
    }

    public synchronized long getCurrentCycleUnitDSMensesStartConfirm(String userName, int cycleNum) {
        CycleUnitDS cycleUnitDS = new CycleUnitDS();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' And cycleNumber = " + cycleNum + " AND ovulationDayUserRecordBasis != -99 ", null);
        while (cursor.moveToNext()) {
            cycleUnitDS.menstruationStartConfirm = cursor.getLong(cursor.getColumnIndex("menstruationStartConfirm"));
        }

        cursor.close();

        return cycleUnitDS.menstruationStartConfirm;

    }

    public synchronized UserUnitDS getALUserData(String userName) {
        AppLog.i("start getALUserData!");

        UserUnitDS userData = new UserUnitDS();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_USERDATA_TABLE_NAME + " WHERE userName = '" + userName + "'", null);

        while (cursor.moveToNext()) {
            userData.validCycleCount = cursor.getInt(cursor.getColumnIndex("validCycleCount"));
            userData.averageMenstruationLength = cursor.getFloat(cursor.getColumnIndex("avgMensesLen"));
            userData.menstruationLengthError = cursor.getFloat(cursor.getColumnIndex("mensesLenError"));
            userData.averageCycleLength = cursor.getFloat(cursor.getColumnIndex("avgCycleLen"));
            userData.cycleLengthError = cursor.getFloat(cursor.getColumnIndex("cycleLenError"));
            userData.averageLuteumPhaseLength = cursor.getFloat(cursor.getColumnIndex("avgLuteumLen"));
            userData.averageOvulationDay = cursor.getFloat(cursor.getColumnIndex("avgOvulationDay"));
            userData.abnormalCaseAlert = cursor.getInt(cursor.getColumnIndex("abCaseAlert"));
        }

        cursor.close();

        return userData;
    }

    public synchronized void initDayUnitDSOutputsList2Memory(String userName) {
        App.dayUnitDSOutputsList.clear();
        App.DayUnitDSOutputMap.clear();

        // periodAchieveForecast <> 99 表示第一个周期被抹去之后以前的全部不显示的标志
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND periodAchieveForecast <> 99 ORDER BY dateStr ASC", null);

        while (cursor.moveToNext()) {
            DayUnitDSOutput dayOutputElement = new DayUnitDSOutput();
            dayOutputElement.date = cursor.getLong(cursor.getColumnIndex("dateStr"));

            if (!DateUtil.isValidDate(dayOutputElement.date)) continue;

            dayOutputElement.periodAchieveForecast = cursor.getInt(cursor.getColumnIndex("periodAchieveForecast"));
            dayOutputElement.periodAchieveConfirm = cursor.getInt(cursor.getColumnIndex("periodAchieveConfirm"));
            dayOutputElement.periodAvoidForecast = cursor.getInt(cursor.getColumnIndex("periodAvoidForecast"));
            dayOutputElement.periodAvoidConfirm = cursor.getInt(cursor.getColumnIndex("periodAvoidConfirm"));
            dayOutputElement.homePageMenstruationEnd = cursor.getInt(cursor.getColumnIndex("homePageMensesEnd"));
            dayOutputElement.homePageOvulation = cursor.getInt(cursor.getColumnIndex("homePageOvulation"));
            dayOutputElement.homePageConceptionChance = cursor.getFloat(cursor.getColumnIndex("homePageConceptChance"));
            dayOutputElement.homePageNextMenstruation = cursor.getInt(cursor.getColumnIndex("homePageNextMenses"));
            dayOutputElement.dayOfCycle = cursor.getInt(cursor.getColumnIndex("dayOfCycle"));

            App.dayUnitDSOutputsList.add(dayOutputElement);
            App.DayUnitDSOutputMap.put(dayOutputElement.date, dayOutputElement);
        }

        cursor.close();
    }

    public synchronized DayUnitDSInput[] getDayInputListFromG1Record(String userName) {
        List<DayUnitDSInput> dayUnitDSInputList = new ArrayList<>();
        //TO-DO-LIST getDayInputListFromG1Record  from G1 record data based on downloaded data
        List<UserRecordData> userRecordDataList = new ArrayList<UserRecordData>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' ORDER BY recordDate ASC", null);
        UserRecordData userRecordData = null;

        while (cursor.moveToNext()) {
            long time = cursor.getLong(cursor.getColumnIndex("recordDate"));

            if (time < DateUtil.getStringToDate("2015-01-01 00:00:00")) continue;
            AppLog.i("Algorithm time = " + DateUtil.getDateTimeStr(time));

            userRecordData = new UserRecordData();
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);

            userRecordData.setRecordDate(time);
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            userRecordDataList.add(userRecordData);
        }

        cursor.close();

        List<UserTemperatureInfo> userTemperatureInfos = getTemperatureList(App.userName, 0);
        if (userRecordDataList.size() > 0) {
            for (int i = 0; i < userRecordDataList.size(); i++) {
                DayUnitDSInput dayUnitDSInput = new DayUnitDSInput();
                long recordDate = userRecordDataList.get(i).getRecordDate();
                long recordDateZeroTime = DateUtil.getDateZeroTime2bit(recordDate);

                for (int j = 0; j < userTemperatureInfos.size(); j++) {
                    long differ = userTemperatureInfos.get(j).getMeasureTime() - recordDateZeroTime;
                    if (differ >= -12 * 3600 && differ < 12 * 3600) {
                        dayUnitDSInput.BBT = (float) userTemperatureInfos.get(j).getTemperature();
                        break;
                    }
                }

                dayUnitDSInput.menstruationRecord = UserRecordData.divideBytes(userRecordDataList.get(i).getMensesInfo(), 2, 0);
                dayUnitDSInput.date = recordDateZeroTime;
                dayUnitDSInput.tempFlag = userRecordDataList.get(i).getSymptomInfo();
                dayUnitDSInputList.add(dayUnitDSInput);
            }
        }

        return dayUnitDSInputList.toArray(new DayUnitDSInput[dayUnitDSInputList.size()]);
    }

    public synchronized DayUnitDSOutput getSelectedDayALDayUnitDSOutput(String userName, long dayTimeStamp) {

        DayUnitDSOutput dayOutputElement = new DayUnitDSOutput();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND dateStr = " + dayTimeStamp + " AND periodAchieveForecast != 99 ", null);

        while (cursor.moveToNext()) {
            dayOutputElement.periodAchieveForecast = cursor.getInt(cursor.getColumnIndex("periodAchieveForecast"));
            dayOutputElement.periodAchieveConfirm = cursor.getInt(cursor.getColumnIndex("periodAchieveConfirm"));
            dayOutputElement.periodAvoidForecast = cursor.getInt(cursor.getColumnIndex("periodAvoidForecast"));
            dayOutputElement.periodAvoidConfirm = cursor.getInt(cursor.getColumnIndex("periodAvoidConfirm"));
            dayOutputElement.homePageMenstruationEnd = cursor.getInt(cursor.getColumnIndex("homePageMensesEnd"));
            dayOutputElement.homePageOvulation = cursor.getInt(cursor.getColumnIndex("homePageOvulation"));
            dayOutputElement.homePageConceptionChance = cursor.getFloat(cursor.getColumnIndex("homePageConceptChance"));
            dayOutputElement.homePageNextMenstruation = cursor.getInt(cursor.getColumnIndex("homePageNextMenses"));
            dayOutputElement.date = cursor.getLong(cursor.getColumnIndex("dateStr"));
            dayOutputElement.dayOfCycle = cursor.getInt(cursor.getColumnIndex("dayOfCycle"));

        }

        cursor.close();

        return dayOutputElement;
    }

    public synchronized List<DayUnitDSOutput> getALDayUnitDSOutputList(String userName, long startTime, long endTime) {

        List<DayUnitDSOutput> dayUnitDSOutputList = new ArrayList<DayUnitDSOutput>();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND dateStr > " + startTime + " AND dateStr < " + endTime + " AND periodAchieveForecast != 99 ", null);

        while (cursor.moveToNext()) {
            DayUnitDSOutput dayOutputElement = new DayUnitDSOutput();

            dayOutputElement.periodAchieveForecast = cursor.getInt(cursor.getColumnIndex("periodAchieveForecast"));
            dayOutputElement.periodAchieveConfirm = cursor.getInt(cursor.getColumnIndex("periodAchieveConfirm"));
            dayOutputElement.periodAvoidForecast = cursor.getInt(cursor.getColumnIndex("periodAvoidForecast"));
            dayOutputElement.periodAvoidConfirm = cursor.getInt(cursor.getColumnIndex("periodAvoidConfirm"));
            dayOutputElement.homePageMenstruationEnd = cursor.getInt(cursor.getColumnIndex("homePageMensesEnd"));
            dayOutputElement.homePageOvulation = cursor.getInt(cursor.getColumnIndex("homePageOvulation"));
            dayOutputElement.homePageConceptionChance = cursor.getFloat(cursor.getColumnIndex("homePageConceptChance"));
            dayOutputElement.homePageNextMenstruation = cursor.getInt(cursor.getColumnIndex("homePageNextMenses"));
            dayOutputElement.date = cursor.getLong(cursor.getColumnIndex("dateStr"));
            dayOutputElement.dayOfCycle = cursor.getInt(cursor.getColumnIndex("dayOfCycle"));

            dayUnitDSOutputList.add(dayOutputElement);
        }

        cursor.close();

        return dayUnitDSOutputList;
    }

    public synchronized List<DayUnitDSOutput> getALDayUnitDSOutputList(String userName) {

        List<DayUnitDSOutput> dayUnitDSOutputList = new ArrayList<DayUnitDSOutput>();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND periodAchieveForecast != 99 ", null);

        while (cursor.moveToNext()) {
            DayUnitDSOutput dayOutputElement = new DayUnitDSOutput();

            dayOutputElement.periodAchieveForecast = cursor.getInt(cursor.getColumnIndex("periodAchieveForecast"));
            dayOutputElement.periodAchieveConfirm = cursor.getInt(cursor.getColumnIndex("periodAchieveConfirm"));
            dayOutputElement.periodAvoidForecast = cursor.getInt(cursor.getColumnIndex("periodAvoidForecast"));
            dayOutputElement.periodAvoidConfirm = cursor.getInt(cursor.getColumnIndex("periodAvoidConfirm"));
            dayOutputElement.homePageMenstruationEnd = cursor.getInt(cursor.getColumnIndex("homePageMensesEnd"));
            dayOutputElement.homePageOvulation = cursor.getInt(cursor.getColumnIndex("homePageOvulation"));
            dayOutputElement.homePageConceptionChance = cursor.getFloat(cursor.getColumnIndex("homePageConceptChance"));
            dayOutputElement.homePageNextMenstruation = cursor.getInt(cursor.getColumnIndex("homePageNextMenses"));
            dayOutputElement.date = cursor.getLong(cursor.getColumnIndex("dateStr"));
            dayOutputElement.dayOfCycle = cursor.getInt(cursor.getColumnIndex("dayOfCycle"));

            dayUnitDSOutputList.add(dayOutputElement);
        }

        cursor.close();

        return dayUnitDSOutputList;
    }

    public synchronized DayUnitDSOutput[] getALDayOutput(String userName) {
        AppLog.i("start getALDayOutput!");

        int dayUnitDSOutputsListLen = App.dayUnitDSOutputsList.size();

        if (dayUnitDSOutputsListLen > 0)
            return App.dayUnitDSOutputsList.toArray(new DayUnitDSOutput[dayUnitDSOutputsListLen]);
        else
            return null;
    }

    public synchronized CycleUnitDS[] getAllMensesConfirmStartHaveALCycleOutput(String userName) {
        AppLog.i("start getALCycleOutput!");

        List<CycleUnitDS> cycleOutputList = new ArrayList<CycleUnitDS>();

        String sqlStr = "SELECT * FROM " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND menstruationStartConfirm > 0" + " AND ovulationDayUserRecordBasis != -99 ";
        Cursor cursor = db.rawQuery(sqlStr, null);

        while (cursor.moveToNext()) {
            CycleUnitDS cycleOutputElement = new CycleUnitDS();

            cycleOutputElement.menstruationStartForecast = cursor.getLong(cursor.getColumnIndex("menstruationStartForecast"));
            cycleOutputElement.menstruationEndForecast = cursor.getLong(cursor.getColumnIndex("menstruationEndForecast"));
            cycleOutputElement.menstruationStartConfirm = cursor.getLong(cursor.getColumnIndex("menstruationStartConfirm"));
            cycleOutputElement.menstruationEndConfirm = cursor.getLong(cursor.getColumnIndex("menstruationEndConfirm"));
            cycleOutputElement.BBTRiseDay = cursor.getLong(cursor.getColumnIndex("BBTRiseDay"));
            cycleOutputElement.peakDay = cursor.getLong(cursor.getColumnIndex("peakDay"));
            cycleOutputElement.ovulationDayForecast = cursor.getLong(cursor.getColumnIndex("ovulationDayForecast"));
            cycleOutputElement.ovulationDayConfirm = cursor.getLong(cursor.getColumnIndex("ovulationDayConfirm"));
            cycleOutputElement.ovulationDayUserRecord = cursor.getLong(cursor.getColumnIndex("ovulationDayUserRecord"));
            cycleOutputElement.ovulationDayBBTRise = cursor.getLong(cursor.getColumnIndex("ovulationDayBBTRise"));
            cycleOutputElement.ovulationDayNextMenstruation = cursor.getLong(cursor.getColumnIndex("ovulationDayNextMenstruation"));
            cycleOutputElement.fertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowStartForecast"));
            cycleOutputElement.fertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowEndForecast"));
            cycleOutputElement.fertileWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowStartConfirm"));
            cycleOutputElement.fertileWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowEndConfirm"));
            cycleOutputElement.dangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowStartForecast"));
            cycleOutputElement.dangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowEndForecast"));
            cycleOutputElement.dangerWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowStartConfirm"));
            cycleOutputElement.dangerWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowEndConfirm"));
            cycleOutputElement.nextMenstruationStartForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationStartForecast"));
            cycleOutputElement.nextMenstruationEndForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationEndForecast"));
            cycleOutputElement.nextOvulationDayForecast = cursor.getLong(cursor.getColumnIndex("nextOvulationDayForecast"));
            cycleOutputElement.nextFertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowStartForecast"));
            cycleOutputElement.nextFertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowEndForecast"));
            cycleOutputElement.nextDangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowStartForecast"));
            cycleOutputElement.nextDangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowEndForecast"));

            cycleOutputElement.cycleNumber = cursor.getInt(cursor.getColumnIndex("cycleNumber"));
            cycleOutputElement.ovulationDayUserRecordBasis = cursor.getInt(cursor.getColumnIndex("ovulationDayUserRecordBasis"));
            cycleOutputElement.showLog();

            cycleOutputList.add(cycleOutputElement);
        }

        cursor.close();

        CycleUnitDS[] cycleOutput = cycleOutputList.toArray(new CycleUnitDS[cycleOutputList.size()]);

        AppLog.i("cycleOutput length = " + cycleOutput.length);
        return cycleOutput;
    }

    public synchronized CycleUnitDS[] getHistoryChangeALCycleOutput(String userName) {
        AppLog.i("start getALCycleOutput!");

        List<CycleUnitDS> cycleOutputList = new ArrayList<CycleUnitDS>();

        String sqlStr = "SELECT * FROM " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND menstruationStartConfirm > 1325376000" + " AND ovulationDayUserRecordBasis != -99 ";
        Cursor cursor = db.rawQuery(sqlStr, null);

        while (cursor.moveToNext()) {
            CycleUnitDS cycleOutputElement = new CycleUnitDS();

            cycleOutputElement.menstruationStartForecast = cursor.getLong(cursor.getColumnIndex("menstruationStartForecast"));
            cycleOutputElement.menstruationEndForecast = cursor.getLong(cursor.getColumnIndex("menstruationEndForecast"));
            cycleOutputElement.menstruationStartConfirm = cursor.getLong(cursor.getColumnIndex("menstruationStartConfirm"));
            cycleOutputElement.menstruationEndConfirm = cursor.getLong(cursor.getColumnIndex("menstruationEndConfirm"));
            cycleOutputElement.BBTRiseDay = cursor.getLong(cursor.getColumnIndex("BBTRiseDay"));
            cycleOutputElement.peakDay = cursor.getLong(cursor.getColumnIndex("peakDay"));
            cycleOutputElement.ovulationDayForecast = cursor.getLong(cursor.getColumnIndex("ovulationDayForecast"));
            cycleOutputElement.ovulationDayConfirm = cursor.getLong(cursor.getColumnIndex("ovulationDayConfirm"));
            cycleOutputElement.ovulationDayUserRecord = cursor.getLong(cursor.getColumnIndex("ovulationDayUserRecord"));
            cycleOutputElement.ovulationDayBBTRise = cursor.getLong(cursor.getColumnIndex("ovulationDayBBTRise"));
            cycleOutputElement.ovulationDayNextMenstruation = cursor.getLong(cursor.getColumnIndex("ovulationDayNextMenstruation"));
            cycleOutputElement.fertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowStartForecast"));
            cycleOutputElement.fertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowEndForecast"));
            cycleOutputElement.fertileWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowStartConfirm"));
            cycleOutputElement.fertileWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowEndConfirm"));
            cycleOutputElement.dangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowStartForecast"));
            cycleOutputElement.dangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowEndForecast"));
            cycleOutputElement.dangerWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowStartConfirm"));
            cycleOutputElement.dangerWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowEndConfirm"));
            cycleOutputElement.nextMenstruationStartForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationStartForecast"));
            cycleOutputElement.nextMenstruationEndForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationEndForecast"));
            cycleOutputElement.nextOvulationDayForecast = cursor.getLong(cursor.getColumnIndex("nextOvulationDayForecast"));
            cycleOutputElement.nextFertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowStartForecast"));
            cycleOutputElement.nextFertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowEndForecast"));
            cycleOutputElement.nextDangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowStartForecast"));
            cycleOutputElement.nextDangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowEndForecast"));

            cycleOutputElement.cycleNumber = cursor.getInt(cursor.getColumnIndex("cycleNumber"));
            cycleOutputElement.ovulationDayUserRecordBasis = cursor.getInt(cursor.getColumnIndex("ovulationDayUserRecordBasis"));
            cycleOutputElement.showLog();

            cycleOutputList.add(cycleOutputElement);
        }

        cursor.close();

        CycleUnitDS[] cycleOutput = cycleOutputList.toArray(new CycleUnitDS[cycleOutputList.size()]);

        AppLog.i("cycleOutput length = " + cycleOutput.length);
        return cycleOutput;
    }

    public synchronized CycleUnitDS[] getALCycleOutput(String userName, String cycleNum) {
        AppLog.i("start getALCycleOutput!");

        List<CycleUnitDS> cycleOutputList = new ArrayList<CycleUnitDS>();

        String sqlStr = "SELECT * FROM " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' " + " AND ovulationDayUserRecordBasis != -99 ";
        if (cycleNum != null)
            sqlStr += "and cycleNumber='" + cycleNum + "'";
        sqlStr += " ORDER BY cycleNumber ASC";
        Cursor cursor = db.rawQuery(sqlStr, null);

        while (cursor.moveToNext()) {
            CycleUnitDS cycleOutputElement = new CycleUnitDS();

            cycleOutputElement.menstruationStartForecast = cursor.getLong(cursor.getColumnIndex("menstruationStartForecast"));
            cycleOutputElement.menstruationEndForecast = cursor.getLong(cursor.getColumnIndex("menstruationEndForecast"));
            cycleOutputElement.menstruationStartConfirm = cursor.getLong(cursor.getColumnIndex("menstruationStartConfirm"));
            cycleOutputElement.menstruationEndConfirm = cursor.getLong(cursor.getColumnIndex("menstruationEndConfirm"));
            cycleOutputElement.BBTRiseDay = cursor.getLong(cursor.getColumnIndex("BBTRiseDay"));
            cycleOutputElement.peakDay = cursor.getLong(cursor.getColumnIndex("peakDay"));
            cycleOutputElement.ovulationDayForecast = cursor.getLong(cursor.getColumnIndex("ovulationDayForecast"));
            cycleOutputElement.ovulationDayConfirm = cursor.getLong(cursor.getColumnIndex("ovulationDayConfirm"));
            cycleOutputElement.ovulationDayUserRecord = cursor.getLong(cursor.getColumnIndex("ovulationDayUserRecord"));
            cycleOutputElement.ovulationDayBBTRise = cursor.getLong(cursor.getColumnIndex("ovulationDayBBTRise"));
            cycleOutputElement.ovulationDayNextMenstruation = cursor.getLong(cursor.getColumnIndex("ovulationDayNextMenstruation"));
            cycleOutputElement.fertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowStartForecast"));
            cycleOutputElement.fertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowEndForecast"));
            cycleOutputElement.fertileWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowStartConfirm"));
            cycleOutputElement.fertileWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowEndConfirm"));
            cycleOutputElement.dangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowStartForecast"));
            cycleOutputElement.dangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowEndForecast"));
            cycleOutputElement.dangerWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowStartConfirm"));
            cycleOutputElement.dangerWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowEndConfirm"));
            cycleOutputElement.nextMenstruationStartForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationStartForecast"));
            cycleOutputElement.nextMenstruationEndForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationEndForecast"));
            cycleOutputElement.nextOvulationDayForecast = cursor.getLong(cursor.getColumnIndex("nextOvulationDayForecast"));
            cycleOutputElement.nextFertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowStartForecast"));
            cycleOutputElement.nextFertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowEndForecast"));
            cycleOutputElement.nextDangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowStartForecast"));
            cycleOutputElement.nextDangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowEndForecast"));

            cycleOutputElement.cycleNumber = cursor.getInt(cursor.getColumnIndex("cycleNumber"));
            cycleOutputElement.ovulationDayUserRecordBasis = cursor.getInt(cursor.getColumnIndex("ovulationDayUserRecordBasis"));
            cycleOutputElement.showLog();

            cycleOutputList.add(cycleOutputElement);
        }

        cursor.close();

        CycleUnitDS[] cycleOutput = cycleOutputList.toArray(new CycleUnitDS[cycleOutputList.size()]);

        AppLog.i("cycleOutput length = " + cycleOutput.length);
        return cycleOutput;
    }

    public void insertUserCompleteTaskIDs(JSONArray jsonArray, int isSynced) {
        db.beginTransaction(); // 开始事务
        try {
            for (int i = 0; i < jsonArray.length(); i++) {
                JSONObject comTasksJSONObj = new JSONObject(jsonArray.get(i).toString());
                if (!comTasksJSONObj.isNull("taskDelete")) {
                    db.execSQL("REPLACE INTO " + DatabaseHelper.COMPLETE_TASK_TABLE_NAME
                            + " VALUES(?, ?, ?, ?, ?)", new Object[]{App.userName, comTasksJSONObj.getString("completeDate"), comTasksJSONObj.getInt("taskID"), comTasksJSONObj.getInt("taskDelete"), isSynced});
                } else {
                    db.execSQL("REPLACE INTO " + DatabaseHelper.COMPLETE_TASK_TABLE_NAME
                            + " VALUES(?, ?, ?, ?, ?)", new Object[]{App.userName, comTasksJSONObj.getString("completeDate"), comTasksJSONObj.getInt("taskID"), 0, isSynced});
                }
            }
            db.setTransactionSuccessful(); // 设置事务成功完成
        } catch (JSONException e) {
            e.printStackTrace();
        } finally {
            db.endTransaction(); // 结束事务
        }
    }

    public void updateUserCompleteTaskID(String userName, String date, int taskID, int isDelete, int isSynced) {
        db.execSQL("REPLACE INTO " + DatabaseHelper.COMPLETE_TASK_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?)", new Object[]{userName, date, taskID, isDelete, isSynced});
    }

    public String getSelectedTaskIds(String date) {
        Cursor cursor = db.rawQuery("SELECT taskID FROM " + DatabaseHelper.COMPLETE_TASK_TABLE_NAME + " WHERE date like '" + date + "%' and isDelete = 0" + " and userName = '" + App.userName + "'", null);

        String value = null;
        while (cursor.moveToNext()) {
            if (value == null) {
                value = "" + cursor.getInt(cursor.getColumnIndex("taskID"));
            } else {
                value = value + "," + cursor.getInt(cursor.getColumnIndex("taskID"));
            }
        }

        cursor.close();

        return value;
    }

    public void insertRecordLH(String userName, String date, String LHPaperID, int result, int isDelete, int isSynced) {
        db.execSQL("REPLACE INTO " + DatabaseHelper.RECORD_LH_TABLE_NAME
                + " VALUES(?, ?, ?,?, ?, ?)", new Object[]{userName, date, LHPaperID, result, isDelete, isSynced});
    }

    /**
     * 更新LH数据
     *
     * @param LHPaperID
     * @param isDelete  1：表示已删除  0：标准未删除
     * @param isSynced  1：表示已同步  0：标准未同步
     */
    public void updateRecordLH(String LHPaperID, int isDelete, int isSynced) {
        db.execSQL("UPDATE " + DatabaseHelper.RECORD_LH_TABLE_NAME
                + " SET isDelete=" + isDelete + ", isSynced=" + isSynced + " WHERE LHPaperID ='" + LHPaperID + "'");
    }

    public List<RecordInfo> getRecordLH(String date, String LHPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date like '" + date + "%' and userName = '" + App.userName + "'" + " and isDelete = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setLHPaperID(cursor.getString(cursor.getColumnIndex(LHPaperID)));
                recordInfo.setLHImgName(cursor.getString(cursor.getColumnIndex(LHPaperID)));
                recordInfo.setLHDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setLHIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setLHIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }

    /**
     * 需要上传的list数据
     *
     * @param LHPaperID
     * @return
     */
    public List<RecordInfo> getNeedSyncedRecordLH(String LHPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE isDelete = 0 and isSynced = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setLHPaperID(cursor.getString(cursor.getColumnIndex(LHPaperID)));
                recordInfo.setLHImgName(cursor.getString(cursor.getColumnIndex(LHPaperID)));
                recordInfo.setLHDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setLHIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setLHIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }


    public void insertRecordHCG(String userName, String date, String HCGPaperID, int result, int isDelete, int isSynced) {
        db.execSQL("REPLACE INTO " + DatabaseHelper.RECORD_HCG_TABLE_NAME
                + " VALUES(?, ?, ?,?, ?, ?)", new Object[]{userName, date, HCGPaperID, result, isDelete, isSynced});
    }

    public void updateRecordHCG(String HCGPaperID, int isDelete, int isSynced) {
        db.execSQL("UPDATE " + DatabaseHelper.RECORD_HCG_TABLE_NAME
                + " SET isDelete=" + isDelete + ", isSynced=" + isSynced + " WHERE HCGPaperID ='" + HCGPaperID + "'");
    }

    public List<RecordInfo> getRecordHCG(String date, String HCGPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_HCG_TABLE_NAME + " WHERE date like '" + date + "%' and userName = '" + App.userName + "'" + " and isDelete = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setHCGPaperID(cursor.getString(cursor.getColumnIndex(HCGPaperID)));
                recordInfo.setHCGImgName(cursor.getString(cursor.getColumnIndex(HCGPaperID)));
                recordInfo.setHCGDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setHCGIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setHCGIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }

    /**
     * 需要上传的list数据
     *
     * @param HCGPaperID
     * @return
     */
    public List<RecordInfo> getNeedSyncedRecordHCG(String HCGPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_HCG_TABLE_NAME + " WHERE isDelete = 0 and isSynced = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setHCGPaperID(cursor.getString(cursor.getColumnIndex(HCGPaperID)));
                recordInfo.setHCGImgName(cursor.getString(cursor.getColumnIndex(HCGPaperID)));
                recordInfo.setHCGDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setHCGIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setHCGIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }

    public void insertRecordBU(String userName, String date, String BUPaperID, int isDelete, int isSynced) {
        db.execSQL("REPLACE INTO " + DatabaseHelper.RECORD_B_TABLE_NAME
                + " VALUES(?, ?, ?, ?, ?)", new Object[]{userName, date, BUPaperID, isDelete, isSynced});
    }

    public void updateRecordBU(String BUID, int isDelete, int isSynced) {
        db.execSQL("UPDATE " + DatabaseHelper.RECORD_B_TABLE_NAME
                + " SET isDelete=" + isDelete + ", isSynced=" + isSynced + " WHERE BUID ='" + BUID + "'");
    }

    public List<RecordInfo> getRecordBU(String date, String BUPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_B_TABLE_NAME + " WHERE date like '" + date + "%' and userName = '" + App.userName + "'" + " and isDelete = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setBUID(cursor.getString(cursor.getColumnIndex(BUPaperID)));
                recordInfo.setBUImgName(cursor.getString(cursor.getColumnIndex(BUPaperID)));
                recordInfo.setBUDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setBUIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setBUIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }

    /**
     * 需要上传的list数据
     *
     * @param BUPaperID
     * @return
     */
    public List<RecordInfo> getNeedSyncedRecordBU(String BUPaperID) {
//        Cursor cursor = db.rawQuery("SELECT " + LHPaperID + " FROM " + DatabaseHelper.RECORD_LH_TABLE_NAME + " WHERE date = '" + date + "'", null);
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_B_TABLE_NAME + " WHERE isDelete = 0 and isSynced = 0", null);

        List<RecordInfo> value = new ArrayList<RecordInfo>();

        if (cursor != null) {
            while (cursor.moveToNext()) {
                RecordInfo recordInfo = new RecordInfo();
                recordInfo.setBUID(cursor.getString(cursor.getColumnIndex(BUPaperID)));
                recordInfo.setBUImgName(cursor.getString(cursor.getColumnIndex(BUPaperID)));
                recordInfo.setBUDate(cursor.getString(cursor.getColumnIndex("date")));
                recordInfo.setBUIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
                recordInfo.setBUIsSynced(cursor.getInt(cursor.getColumnIndex("isSynced")));
                value.add(recordInfo);
            }
            cursor.close();
        }
        return value;
    }

    public void closeDB() {
        AppLog.i("DBManager --> closeDB");
        // 释放数据库资源
        db.close();
    }
    /**
     * *****************
     * sync DB 操作
     * *****************
     */

    /**
     * 公共方法
     *
     * @param table
     * @param userName
     */
    public synchronized void updateDBSyncFlag(String table, String userName) {
        AppLog.i("start updateDBSyncFlag!");
        ContentValues values = new ContentValues();
        values.put("isSynced", 1);
        db.update(table, values, "userName = ? AND isSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncTaskItemFlag(String userName) {
        AppLog.i("start updateSyncTaskItemFlag!");
        ContentValues values = new ContentValues();
        values.put("isTaskIDSynced", 1);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ? AND isTaskIDSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncMACAddressFlag(String userName) {
        AppLog.i("start updateSyncTaskItemFlag!");
        ContentValues values = new ContentValues();
        values.put("isMACAddressSynced", 1);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ? AND isMACAddressSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncNickNameFlag(String userName) {
        AppLog.i("start updateSyncNickNameFlag!");
        ContentValues values = new ContentValues();
        values.put("isNickNameSynced", 1);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ? AND isNickNameSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncStateFlag(String userName) {
        AppLog.i("start updateSyncStateFlag!");
        ContentValues values = new ContentValues();
        values.put("isStateSynced", 1);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ? AND isStateSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncHealthInfoFlag(String userName) {
        AppLog.i("start updateSyncHealthInfoFlag!");
        ContentValues values = new ContentValues();
        values.put("isHealthInfoSynced", 1);
        db.update(DatabaseHelper.USER_PREFERENCE_TABLE_NAME, values, "userName = ? AND isHealthInfoSynced = ?", new String[]{userName, "0"});
    }

    public synchronized void updateSyncRecordInfoFlag(String userName) {
        AppLog.i("start updateSyncedRecordInfoFlag");
        ContentValues values = new ContentValues();
        values.put("isSynced", 1);
        db.update(DatabaseHelper.TEMPERATURE_TABLE_NAME, values, "userName = ? AND isSynced = ?", new String[]{userName, "0"});
        db.update(DatabaseHelper.RECORD_INFORMATION_TABLE_NAME, values, "userName = ? AND isSynced = ?", new String[]{userName, "0"});
    }

    public synchronized List<CollectionBean> getUnSyncedCollectionArticles(String userName) {
        AppLog.i("start getUnSyncedCollectionArticles!");

        List<CollectionBean> collectionBeanList = new ArrayList<>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.COLLECTION_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0" + " and collectionDelete = 0", null);

        while (cursor.moveToNext()) {
            CollectionBean collectionBean = new CollectionBean();

            String collectionID = cursor.getString(cursor.getColumnIndex("collectionID"));
            String collectionTitle = cursor.getString(cursor.getColumnIndex("articleTitle"));
            int articleId = cursor.getInt(cursor.getColumnIndex("articleId"));
            String collectionDate = cursor.getString(cursor.getColumnIndex("collectionDate"));
            int collectionDelete = cursor.getInt(cursor.getColumnIndex("collectionDelete"));

            collectionBean.setCollectionID(collectionID);
            collectionBean.setCollectionTitle(collectionTitle);
            collectionBean.setArticleId(articleId);
            collectionBean.setCollectionDate(collectionDate);
            collectionBean.setCollectionDelete(collectionDelete);

            collectionBeanList.add(collectionBean);
        }

        cursor.close();

        return collectionBeanList;
    }

    public synchronized List<TasksUtil> getUnSyncedCompleteTask(String userName) {

        List<TasksUtil> completeTaskList = new ArrayList<TasksUtil>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.COMPLETE_TASK_TABLE_NAME + " WHERE userName = '" + userName + "' and isSynced = 0" + " and isDelete = 0", null);

        while (cursor.moveToNext()) {
            TasksUtil tasksUtil = new TasksUtil();

            String date = cursor.getString(cursor.getColumnIndex("date"));
            int taskID = cursor.getInt(cursor.getColumnIndex("taskID"));
            int isDelete = cursor.getInt(cursor.getColumnIndex("isDelete"));

            tasksUtil.setCompleteDate(date);
            tasksUtil.setTaskID(taskID);
            tasksUtil.setTaskDelete(isDelete);

            completeTaskList.add(tasksUtil);
        }

        cursor.close();

        return completeTaskList;
    }

    public synchronized JSONObject getUnSyncedALUserData(String userName) {
        UserUnitDS userData = new UserUnitDS();
        JSONObject jsonObject = new JSONObject();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_USERDATA_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0", null);

        while (cursor.moveToNext()) {
            userData.validCycleCount = cursor.getInt(cursor.getColumnIndex("validCycleCount"));
            userData.averageMenstruationLength = cursor.getFloat(cursor.getColumnIndex("avgMensesLen"));
            userData.menstruationLengthError = cursor.getFloat(cursor.getColumnIndex("mensesLenError"));
            userData.averageCycleLength = cursor.getFloat(cursor.getColumnIndex("avgCycleLen"));
            userData.cycleLengthError = cursor.getFloat(cursor.getColumnIndex("cycleLenError"));
            userData.averageLuteumPhaseLength = cursor.getFloat(cursor.getColumnIndex("avgLuteumLen"));
            userData.averageOvulationDay = cursor.getFloat(cursor.getColumnIndex("avgOvulationDay"));
            userData.abnormalCaseAlert = cursor.getInt(cursor.getColumnIndex("abCaseAlert"));

            try {
                jsonObject.put("validCycleCount", userData.validCycleCount);
                jsonObject.put("averageMenstruationLength", String.valueOf(userData.averageMenstruationLength));
                jsonObject.put("menstruationErrorLength", String.valueOf(userData.menstruationLengthError));
                jsonObject.put("averageCycleLength", String.valueOf(userData.averageCycleLength));
                jsonObject.put("cycleErrorLength", String.valueOf(userData.cycleLengthError));
                jsonObject.put("averageLuteumPhaseLength", String.valueOf(userData.averageLuteumPhaseLength));
                jsonObject.put("abnormalCaseAlert", userData.abnormalCaseAlert);

            } catch (JSONException e) {
                e.printStackTrace();
            }
        }

        cursor.close();

        return jsonObject;
    }

    public synchronized JSONArray getUnSyncedALDayOutput(String userName) {

        JSONArray jsonArrayCycleDatas = new JSONArray();
        JSONObject jsonObject;
        DayUnitDSOutput dayOutputElement = new DayUnitDSOutput();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_DAYOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0", null);

        while (cursor.moveToNext()) {
            dayOutputElement.date = cursor.getLong(cursor.getColumnIndex("dateStr"));

            if (!DateUtil.isValidDate(dayOutputElement.date))
                continue;

            jsonObject = new JSONObject();

            dayOutputElement.periodAchieveForecast = cursor.getInt(cursor.getColumnIndex("periodAchieveForecast"));
            dayOutputElement.periodAchieveConfirm = cursor.getInt(cursor.getColumnIndex("periodAchieveConfirm"));
            dayOutputElement.periodAvoidForecast = cursor.getInt(cursor.getColumnIndex("periodAvoidForecast"));
            dayOutputElement.periodAvoidConfirm = cursor.getInt(cursor.getColumnIndex("periodAvoidConfirm"));
            dayOutputElement.homePageMenstruationEnd = cursor.getInt(cursor.getColumnIndex("homePageMensesEnd"));
            dayOutputElement.homePageOvulation = cursor.getInt(cursor.getColumnIndex("homePageOvulation"));
            dayOutputElement.homePageConceptionChance = cursor.getFloat(cursor.getColumnIndex("homePageConceptChance"));
            dayOutputElement.homePageNextMenstruation = cursor.getInt(cursor.getColumnIndex("homePageNextMenses"));
            dayOutputElement.dayOfCycle = cursor.getInt(cursor.getColumnIndex("dayOfCycle"));

            try {
                String str = DateUtil.getDateTimeStr2bit(dayOutputElement.date);
                jsonObject.put("infoDate", str);
                jsonObject.put("periodAchieveForecast", String.valueOf(dayOutputElement.periodAchieveForecast));
                jsonObject.put("periodAchieveConfirm", String.valueOf(dayOutputElement.periodAchieveConfirm));
                jsonObject.put("periodAvoidForecast", String.valueOf(dayOutputElement.periodAvoidForecast));
                jsonObject.put("periodAvoidConfirm", String.valueOf(dayOutputElement.periodAvoidConfirm));
                jsonObject.put("homePageMenstruationEnd", String.valueOf(dayOutputElement.homePageMenstruationEnd));
                jsonObject.put("homePageOvulation", String.valueOf(dayOutputElement.homePageOvulation));
                jsonObject.put("homePageConceptionChance", String.valueOf(dayOutputElement.homePageConceptionChance));
                jsonObject.put("homePageNextMenstruation", String.valueOf(dayOutputElement.homePageNextMenstruation));
                jsonObject.put("dayOfCycle", String.valueOf(dayOutputElement.dayOfCycle));

            } catch (JSONException e) {
                e.printStackTrace();
            }

            jsonArrayCycleDatas.put(jsonObject);
        }

        cursor.close();

        return jsonArrayCycleDatas;
    }

    public synchronized JSONArray getUnSyncedALCycleOutput(String userName) {
        JSONArray jsonArrayCycleDatas = new JSONArray();
        JSONObject jsonObject;
        CycleUnitDS cycleOutputElement = new CycleUnitDS();

        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.AL_CYCLEOUTPUT_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0", null);

        while (cursor.moveToNext()) {

            cycleOutputElement.cycleNumber = cursor.getInt(cursor.getColumnIndex("cycleNumber"));

            if (cycleOutputElement.cycleNumber == -10)
                continue;

            jsonObject = new JSONObject();

            cycleOutputElement.menstruationStartForecast = cursor.getLong(cursor.getColumnIndex("menstruationStartForecast"));
            cycleOutputElement.menstruationEndForecast = cursor.getLong(cursor.getColumnIndex("menstruationEndForecast"));
            cycleOutputElement.menstruationStartConfirm = cursor.getLong(cursor.getColumnIndex("menstruationStartConfirm"));
            cycleOutputElement.menstruationEndConfirm = cursor.getLong(cursor.getColumnIndex("menstruationEndConfirm"));
            cycleOutputElement.BBTRiseDay = cursor.getLong(cursor.getColumnIndex("BBTRiseDay"));
            cycleOutputElement.peakDay = cursor.getLong(cursor.getColumnIndex("peakDay"));
            cycleOutputElement.ovulationDayForecast = cursor.getLong(cursor.getColumnIndex("ovulationDayForecast"));
            cycleOutputElement.ovulationDayConfirm = cursor.getLong(cursor.getColumnIndex("ovulationDayConfirm"));
            cycleOutputElement.ovulationDayUserRecord = cursor.getLong(cursor.getColumnIndex("ovulationDayUserRecord"));
            cycleOutputElement.ovulationDayUserRecordBasis = cursor.getInt(cursor.getColumnIndex("ovulationDayUserRecordBasis"));
            cycleOutputElement.ovulationDayBBTRise = cursor.getLong(cursor.getColumnIndex("ovulationDayBBTRise"));
            cycleOutputElement.ovulationDayNextMenstruation = cursor.getLong(cursor.getColumnIndex("ovulationDayNextMenstruation"));
            cycleOutputElement.fertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowStartForecast"));
            cycleOutputElement.fertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("fertileWindowEndForecast"));
            cycleOutputElement.fertileWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowStartConfirm"));
            cycleOutputElement.fertileWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("fertileWindowEndConfirm"));
            cycleOutputElement.dangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowStartForecast"));
            cycleOutputElement.dangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("dangerWindowEndForecast"));
            cycleOutputElement.dangerWindowStartConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowStartConfirm"));
            cycleOutputElement.dangerWindowEndConfirm = cursor.getLong(cursor.getColumnIndex("dangerWindowEndConfirm"));
            cycleOutputElement.nextMenstruationStartForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationStartForecast"));
            cycleOutputElement.nextMenstruationEndForecast = cursor.getLong(cursor.getColumnIndex("nextMenstruationEndForecast"));
            cycleOutputElement.nextOvulationDayForecast = cursor.getLong(cursor.getColumnIndex("nextOvulationDayForecast"));
            cycleOutputElement.nextFertileWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowStartForecast"));
            cycleOutputElement.nextFertileWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextFertileWindowEndForecast"));
            cycleOutputElement.nextDangerWindowStartForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowStartForecast"));
            cycleOutputElement.nextDangerWindowEndForecast = cursor.getLong(cursor.getColumnIndex("nextDangerWindowEndForecast"));

            try {
                jsonObject.put("cycleNumber", String.valueOf(cycleOutputElement.cycleNumber));
                jsonObject.put("menstruationStartForecast", String.valueOf(cycleOutputElement.menstruationStartForecast));
                jsonObject.put("menstruationEndForecast", String.valueOf(cycleOutputElement.menstruationEndForecast));
                jsonObject.put("menstruationStartConfirm", String.valueOf(cycleOutputElement.menstruationStartConfirm));
                jsonObject.put("menstruationEndConfirm", String.valueOf(cycleOutputElement.menstruationEndConfirm));
                jsonObject.put("bBTRiseDay", String.valueOf(cycleOutputElement.BBTRiseDay));
                jsonObject.put("peakDay", String.valueOf(cycleOutputElement.peakDay));
                jsonObject.put("ovulationDayForecast", String.valueOf(cycleOutputElement.ovulationDayForecast));
                jsonObject.put("ovulationDayConfirm", String.valueOf(cycleOutputElement.ovulationDayConfirm));
                jsonObject.put("ovulationDayUserRecord", String.valueOf(cycleOutputElement.ovulationDayUserRecord));
                jsonObject.put("ovulationDayUserRecordBasis", String.valueOf(cycleOutputElement.ovulationDayUserRecordBasis));
                jsonObject.put("ovulationDayBBTRiseDay", String.valueOf(cycleOutputElement.ovulationDayBBTRise));
                jsonObject.put("ovulationDayNextMenstruation", String.valueOf(cycleOutputElement.ovulationDayNextMenstruation));
                jsonObject.put("fertileStartForecast", String.valueOf(cycleOutputElement.fertileWindowStartForecast));
                jsonObject.put("fertileEndForecast", String.valueOf(cycleOutputElement.fertileWindowEndForecast));
                jsonObject.put("fertileStartConfirm", String.valueOf(cycleOutputElement.fertileWindowStartConfirm));
                jsonObject.put("fertileEndConfirm", String.valueOf(cycleOutputElement.fertileWindowEndConfirm));
                jsonObject.put("dangerStartForecast", String.valueOf(cycleOutputElement.dangerWindowStartForecast));
                jsonObject.put("dangerEndForecast", String.valueOf(cycleOutputElement.dangerWindowEndForecast));
                jsonObject.put("dangerStartConfirm", String.valueOf(cycleOutputElement.dangerWindowStartConfirm));
                jsonObject.put("dangerEndConfirm", String.valueOf(cycleOutputElement.dangerWindowEndConfirm));
                jsonObject.put("nextMenstruationStartForecast", String.valueOf(cycleOutputElement.nextMenstruationStartForecast));
                jsonObject.put("nextMenstruationEndForecast", String.valueOf(cycleOutputElement.nextMenstruationEndForecast));
                jsonObject.put("nextOvulateForecast", String.valueOf(cycleOutputElement.nextOvulationDayForecast));
                jsonObject.put("nextFertileStartForecast", String.valueOf(cycleOutputElement.nextFertileWindowStartForecast));
                jsonObject.put("nextFertileEndForecast", String.valueOf(cycleOutputElement.nextFertileWindowEndForecast));
                jsonObject.put("nextDangerStartForecast", String.valueOf(cycleOutputElement.nextDangerWindowStartForecast));
                jsonObject.put("nextDangerEndForecast", String.valueOf(cycleOutputElement.nextDangerWindowEndForecast));

            } catch (JSONException e) {
                e.printStackTrace();
            }

            jsonArrayCycleDatas.put(jsonObject);
        }

        cursor.close();

        return jsonArrayCycleDatas;
    }

    public synchronized String getUnSyncedTaskItems(String userName) {

        String taskItems = null;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isTaskIDSynced = 0", null);

        while (cursor.moveToNext()) {
            taskItems = cursor.getString(cursor.getColumnIndex("taskIDs"));
        }

        cursor.close();

        return taskItems;
    }

    public synchronized String getUnSyncedMacAddress(String userName) {

        String macAddress = null;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isMACAddressSynced = 0", null);

        while (cursor.moveToNext()) {
            macAddress = cursor.getString(cursor.getColumnIndex("macAddress"));
        }

        cursor.close();

        return macAddress;
    }

    public synchronized String getUnSyncedNickName(String userName) {

        String nickName = null;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isNickNameSynced = 0", null);

        while (cursor.moveToNext()) {
            nickName = cursor.getString(cursor.getColumnIndex("nickName"));
        }

        cursor.close();

        return nickName;
    }

    public synchronized int getUnSyncedState(String userName) {

        int state = -1;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isStateSynced = 0", null);

        while (cursor.moveToNext()) {
            state = cursor.getInt(cursor.getColumnIndex("state"));
        }

        cursor.close();

        return state;
    }
///系统默认全部任务

    public void initTaskDetail(int sysTaskID, String userName, int isDelete, int isChoose,
                               String taskDetail, String taskDetailEn, String glossary,
                               String glossaryEn, String glossaryColor, String BgColor, int glossaryBegin,
                               int glossaryEnd, int glossaryBeginEn,
                               int glossaryEndEn, String date, String task, String taskEn) {

        db.execSQL("REPLACE INTO " + DatabaseHelper.SYS_TASK_TABLE_NAME
                        + " VALUES(?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)",
                new Object[]{sysTaskID, userName, isDelete, isChoose, taskDetail,
                        taskDetailEn, glossary, glossaryEn, glossaryColor,
                        BgColor, glossaryBegin, glossaryEnd, glossaryBeginEn, glossaryEndEn, date, task, taskEn});


    }

    public synchronized List<HomeSysTask> getHomeSysTask() {

        List<HomeSysTask> list = new ArrayList<>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.SYS_TASK_TABLE_NAME, null);

        while (cursor.moveToNext()) {
            HomeSysTask homeSysTask = new HomeSysTask();
            homeSysTask.setSysTaskID(cursor.getInt(cursor.getColumnIndex("sysTaskID")));
            homeSysTask.setUserName(cursor.getString(cursor.getColumnIndex("userName")));
            homeSysTask.setIsDelete(cursor.getInt(cursor.getColumnIndex("isDelete")));
            homeSysTask.setIsChoose(cursor.getInt(cursor.getColumnIndex("isChoose")));
            homeSysTask.setTaskDetail(cursor.getString(cursor.getColumnIndex("taskDetail")));
            homeSysTask.setTaskDetailEn(cursor.getString(cursor.getColumnIndex("taskDetailEn")));
            homeSysTask.setGlossary(cursor.getString(cursor.getColumnIndex("glossary")));
            homeSysTask.setGlossaryEn(cursor.getString(cursor.getColumnIndex("glossaryEn")));
            homeSysTask.setGlossaryColor(cursor.getString(cursor.getColumnIndex("glossaryColor")));
            homeSysTask.setBgColor(cursor.getString(cursor.getColumnIndex("bgColor")));
            homeSysTask.setGlossaryBeginEn(cursor.getInt(cursor.getColumnIndex("glossaryBeginEn")));
            homeSysTask.setGlossaryEndEn(cursor.getInt(cursor.getColumnIndex("glossaryEndEn")));
            homeSysTask.setGlossaryBegin(cursor.getInt(cursor.getColumnIndex("glossaryBegin")));
            homeSysTask.setGlossaryEnd(cursor.getInt(cursor.getColumnIndex("glossaryEnd")));
            homeSysTask.setDate(cursor.getString(cursor.getColumnIndex("date")));
            homeSysTask.setTask(cursor.getString(cursor.getColumnIndex("task")));
            homeSysTask.setTaskEn(cursor.getString(cursor.getColumnIndex("taskEn")));


            list.add(homeSysTask);
        }
        cursor.close();

        return list;
    }

    public synchronized HealthInfo getUnSyncedHealthInfo(String userName) {

        HealthInfo healthInfo = null;
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.USER_PREFERENCE_TABLE_NAME + " WHERE userName = '" + userName + "' AND isHealthInfoSynced = 0", null);

        while (cursor.moveToNext()) {
            healthInfo = new HealthInfo();

            healthInfo.setBirthday(cursor.getString(cursor.getColumnIndex("birthday")));
            healthInfo.setPeriodLen(cursor.getInt(cursor.getColumnIndex("periodLen")));
            healthInfo.setMensesLen(cursor.getInt(cursor.getColumnIndex("mensesLen")));
            healthInfo.setMensesType(cursor.getInt(cursor.getColumnIndex("mensesType")));
            healthInfo.setLastPeriodDate(cursor.getString(cursor.getColumnIndex("lastPeriodDate")));
        }

        cursor.close();

        return healthInfo;
    }


    public synchronized List<UserRecordData> getUnSyncedRecordDataList(String userName) {

        List<UserRecordData> userRecordDataList = new ArrayList<UserRecordData>();
        Cursor cursor = db.rawQuery("SELECT * FROM " + DatabaseHelper.RECORD_INFORMATION_TABLE_NAME + " WHERE userName = '" + userName + "' AND isSynced = 0" + " AND recordDate > 1420070400", null);
        UserRecordData userRecordData = null;

        while (cursor.moveToNext()) {
            userRecordData = new UserRecordData();
            userRecordData.setId(cursor.getString(cursor.getColumnIndex("id")));
            userRecordData.setUserName(App.userName);
            userRecordData.setRecordDate(cursor.getLong(cursor.getColumnIndex("recordDate")));
            userRecordData.setRecordEditDate(cursor.getLong(cursor.getColumnIndex("recordEditDate")));
            userRecordData.setSymptomInfo(cursor.getInt(cursor.getColumnIndex("symptomInfo")));
            userRecordData.setMucusInfo(cursor.getInt(cursor.getColumnIndex("mucusInfo")));
            userRecordData.setMensesInfo(cursor.getInt(cursor.getColumnIndex("mensesInfo")));
            userRecordData.setCopulationInfo(cursor.getInt(cursor.getColumnIndex("copulationInfo")));
            userRecordData.setOvulationInfo(cursor.getInt(cursor.getColumnIndex("ovulationInfo")));
            userRecordData.setSexTime(cursor.getLong(cursor.getColumnIndex("sexTime")));
            userRecordData.setMemoInfo(cursor.getString(cursor.getColumnIndex("memeoInfo")));
            //userRecordData.setIsSynced(1);
            userRecordDataList.add(userRecordData);
        }
        cursor.close();

        //添加温度信息
        for (int i = 0; i < userRecordDataList.size(); i++) {
            long date = userRecordDataList.get(i).getRecordDate();
            List<UserTemperatureInfo> userTemperatureInfoList = getSelectedDayTemperature(App.userName, DateUtil.getDateStr2bit(date));

            if (userTemperatureInfoList.size() > 0) {
                UserTemperatureInfo[] userTemperatureInfos = new UserTemperatureInfo[userTemperatureInfoList.size()];
                for (int j = 0; j < userTemperatureInfoList.size(); j++) {
                    userTemperatureInfos[j] = userTemperatureInfoList.get(j);
                }
                userRecordDataList.get(i).setUserTemperatureInfos(userTemperatureInfos);
            }
        }

        return userRecordDataList;
    }

}
